#ifndef VSSCENERENDER_H
#define VSSCENERENDER_H
#include "VS2DTexture.h"
#include "VSDepthStencil.h"
#include "VSSpatial.h"
#include "VSScene.h"
#include "VSPostEffectSet.h"
#include "VSDebugDraw.h"
#include "VSRenderTarget.h"
namespace VSEngine2
{
	class VSGRAPHIC_API VSSceneRenderInterface : public VSReference,public VSMemObject
	{
	public:
		VSSceneRenderInterface();
		virtual ~VSSceneRenderInterface() = 0;
		

		

		

		virtual VSRenderTarget * GetRenderTarget(unsigned int uiIndex);

		inline void SetParam(unsigned int uiClearFlag,VSColorRGBA ClearColorRGBA,VSREAL fClearDepth,
						unsigned int uiClearStencil,bool bUseViewClear = false)
		{
			m_uiClearFlag = uiClearFlag;
			m_ClearColorRGBA = ClearColorRGBA;
			m_fClearDepth = fClearDepth;
			m_uiClearStencil = uiClearStencil;
			m_bUseViewPortClear = bUseViewClear;

		}
		virtual bool AddRenderTarget(VSRenderTarget * pTarget);
		void SetUseState(VSRenderState & RenderState,unsigned int uiRenderStateInheritFlag);
		void ClearUseState();
	protected:
		VSArray<VSRenderTargetPtr> m_pTargetArray;
		
		unsigned int m_uiClearFlag;
		VSColorRGBA m_ClearColorRGBA;
		VSREAL m_fClearDepth;
		unsigned int m_uiClearStencil;
		bool  m_bUseViewPortClear;
		VSRenderState m_UseState;
		unsigned int m_uiRenderStateInheritFlag;
		unsigned int m_uiRTWidth;
		unsigned int m_uiRTHeight;
	};
	typedef VSPointer<VSSceneRenderInterface> VSSceneRenderInterfacePtr;
	
	class VSGRAPHIC_API VSSceneRender : public VSSceneRenderInterface
	{
	public:
		VSSceneRender();
		virtual ~VSSceneRender();
		
		inline VSDepthStencil * GetDepthStencil(unsigned int uiRenderGroup)const
		{
			if (uiRenderGroup >= VSCuller::RG_MAX)
			{
				return false;
			}
			return m_pDepthStencil[uiRenderGroup];
		}	
		virtual bool SetDepthStencil(VSDepthStencil * pDepthStencil,unsigned int uiRenderGroup);
		virtual bool Draw(VSCuller & Culler,double dAppTime);
		virtual void ClearRTAndDepth();
	protected:
		virtual bool OnDraw(VSCuller & Culler,unsigned int uiRenderGroup) = 0;
		VSDepthStencilPtr m_pDepthStencil[VSCuller::RG_MAX];
		
	};
	typedef VSPointer<VSSceneRender> VSSceneRenderPtr;

	class VSGRAPHIC_API VSMaterialSceneRender : public VSSceneRender
	{
	public:
		VSMaterialSceneRender();
		virtual ~VSMaterialSceneRender();
	protected:
		virtual bool OnDraw(VSCuller & Culler,unsigned int uiRenderGroup);
	};
	typedef VSPointer<VSMaterialSceneRender> VSMaterialSceneRenderPtr;

	class VSGRAPHIC_API VSDebugDrawSceneRender : public VSSceneRender
	{
	public:
		VSDebugDrawSceneRender();
		virtual ~VSDebugDrawSceneRender();
		inline VSDebugDraw * GetDebugDraw(unsigned int uiRenderGroup)
		{
			if (uiRenderGroup >= VSCuller::RG_MAX)
			{
				return false;
			}
			return m_pDebugDraw[uiRenderGroup];
		}
	protected:
		virtual bool OnDraw(VSCuller & Culler,unsigned int uiRenderGroup);
		VSDebugDrawPtr m_pDebugDraw[VSCuller::RG_MAX];
	};
	typedef VSPointer<VSDebugDrawSceneRender> VSDebugDrawSceneRenderPtr;

	class VSGRAPHIC_API VSNormalDepthSceneRender : public VSSceneRender
	{
	public:
		VSNormalDepthSceneRender();
		virtual ~VSNormalDepthSceneRender();
	protected:
		virtual bool OnDraw(VSCuller & Culler,unsigned int uiRenderGroup);
	};
	typedef VSPointer<VSNormalDepthSceneRender> VSNormalDepthSceneRenderPtr;

	class VSGRAPHIC_API VSPrezSceneRender : public VSSceneRender
	{
	public:
		VSPrezSceneRender();
		virtual ~VSPrezSceneRender();
	protected:
		virtual bool OnDraw(VSCuller & Culler,unsigned int uiRenderGroup);
	};
	typedef VSPointer<VSPrezSceneRender> VSPrezSceneRenderPtr;

	class VSGRAPHIC_API VSPostEffectSceneRender : public VSSceneRenderInterface
	{
	protected:
		VSTexAllStatePtr m_pTexAllState;
		virtual bool OnDraw(VSCuller & Culler) = 0;
		VSDepthStencilPtr m_pDepthStencil;
	public:
		virtual bool SetDepthStencil(VSDepthStencil * pDepthStencil);
		VSDepthStencil * GetDepthStencil()const
		{
			return m_pDepthStencil;
		}
		VSPostEffectSceneRender();
		virtual ~VSPostEffectSceneRender();
		virtual void CreateRT(unsigned int uiWidth,unsigned int uiHeight);
		virtual bool IsReCreate(unsigned int uiWidth,unsigned int uiHeight);
		virtual void SetSourceTarget(VSTexture * pTexture);
		virtual bool Draw(VSCuller & Culler,double dAppTime);
	};
	typedef VSPointer<VSPostEffectSceneRender> VSPostEffectSceneRenderPtr;
	class VSGRAPHIC_API VSPEBlurSceneRender : public VSPostEffectSceneRender
	{
	protected:
		
	public:
		VSPEBlurSceneRender();
		virtual ~VSPEBlurSceneRender();

	};
	typedef VSPointer<VSPEBlurSceneRender> VSPEBlurSceneRenderPtr;
	class VSGRAPHIC_API VSPEGraySceneRender : public VSPostEffectSceneRender
	{
	protected:
		VSCustomMaterialPtr m_pGrayMaterial;
		virtual bool OnDraw(VSCuller & Culler);
	public:
		VSPEGraySceneRender();
		virtual ~VSPEGraySceneRender();	
		virtual void SetSourceTarget(VSTexture * pTexture);
	};
	class VSGRAPHIC_API VSPEScreenQuadSceneRender : public VSPostEffectSceneRender
	{
	protected:
		VSCustomMaterialPtr m_pScreenQuadMaterial;
		virtual bool OnDraw(VSCuller & Culler);
	public:
		VSPEScreenQuadSceneRender();
		virtual ~VSPEScreenQuadSceneRender();
		virtual void SetSourceTarget(VSTexture * pTexture);
		virtual void CreateRT(unsigned int uiWidth,unsigned int uiHeight);
		virtual bool IsReCreate(unsigned int uiWidth,unsigned int uiHeight);
	};
	typedef VSPointer<VSPEScreenQuadSceneRender> VSPEScreenQuadSceneRenderPtr;
	class VSGRAPHIC_API VSShadowMapSceneRender : public VSSceneRenderInterface
	{
	public:
		VSShadowMapSceneRender();
		virtual ~VSShadowMapSceneRender();	
		
	protected:
		virtual bool OnDraw(VSCuller & Culler);
	};
	typedef VSPointer<VSShadowMapSceneRender> VSShadowMapSceneRenderPtr;

}
#endif